package com.app.web.order.job;

import com.alibaba.fastjson.JSON;
import com.app.base.EnumType;
import com.app.utils.base.j2se.*;
import com.app.utils.task.TaskDao;
import com.app.web.order.OrderDao;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

/**
 * Description
 * Created by 王伟
 * Date create on 14:40 2019/12/18.
 */
@Service
public class OrderAnalyService {
    @Autowired
    private TaskDao taskDao;
    @Autowired
    private OrderAnalyDao orderAnalyDao;
    @Autowired
    private OrderDao orderDao;

    /**
     * 获取记录值
     * @param source_tab_name 源数据表
     * @param analy_tab_name 分析数据表
     * @return
     */
    public long getRecord(String source_tab_name,String analy_tab_name){
        return taskDao.getRecord(source_tab_name, analy_tab_name);
    }

    //获取订单数据
    public List<Map<String,Object>> getGoodsOrderListByRecord(long record){
        return orderAnalyDao.getGoodsOrderListByRecord(record);
    }

    /* 订单分佣数据 */
    public List<Map<String,Object>> getOrderExpectList(long record){
        return orderAnalyDao.getOrderExpectList(record);
    }

    //根据状态查询订单
    public List<Map<String, Object>> getOrderByStatus(long record,int type){
        return orderAnalyDao.getOrderByStatus(record, type);
    }

    //查询用户可提现金额数据
    public List<Map<String, Object>> getUserMoneyWithdrawalExpect(Map<String, Object> paramMap){
        return orderAnalyDao.getUserMoneyWithdrawalExpect(paramMap);
    }

    /**
     * 获取订单明细 根据记录值 和日期
     * @param record 记录值
     * @return
     */
    public List<Map<String,Object>> getUserMoneyDetailExpectList(long record){
        Map<String,Object> orderParamMap = new HashMap<>();
        orderParamMap.put("record",record);
        return orderAnalyDao.getUserMoneyDetailExpectList(orderParamMap);
    }

    /**
     * 获取订单明细 根据记录值 和日期
     * @param record 记录值
     * @return
     */
    public List<Map<String,Object>> getUserMoneyDetailInvalidExpectList(long record){
        Map<String,Object> orderParamMap = new HashMap<>();
        orderParamMap.put("record",record);
        return orderAnalyDao.getUserMoneyDetailInvalidExpectList(orderParamMap);
    }

    /**
     * 订单分佣明细----OrderPromotionDetails
     * 更新用户金额
     * @param orderList
     * @return
     */
    @Transactional
    public void updateUserMoney(List<Map<String, Object>> orderList, String source_tab_name, String analy_tab_name){
        long record = 0;
        for(Map<String,Object> orderMap : orderList){
            record = Convert.objToLong(orderMap.get("id"));
            String order_sn = Convert.objToStr(orderMap.get("order_sn"));
            //查询该订单是否已经处理过 如果已经处理过 则不再进行处理
            if(orderAnalyDao.getUserMoneyDetailExpect(order_sn)>0){
                continue;
            }
            //更新用户余额及明细
            if(Common.isNotEmpty(orderMap.get("mcode")))updateUserMoney(orderMap);
        }
        //更新分析记录值
        if(record>0) {
            taskDao.updateRecord(record, source_tab_name, analy_tab_name);
        }
    }

    private void updateUserMoney(Map<String, Object> orderMap){
        int role = Convert.objToInt(orderMap.get("role"));
        int prole = Convert.objToInt(orderMap.get("mcode_role"));
        if(0==prole || prole==5)return;
        /* 奖励金额 */
        int yongjin = 0;
        // 差价商品正常计算   特定商品每单位2元
        if(Convert.objToInt(orderMap.get("goods_is_discount"))==1){
            if(prole == EnumType.ROLE.超级黑卡.getRole()){
                // 超级黑卡推荐超级黑卡 固定2元一单位
                if(role == EnumType.ROLE.超级黑卡.getRole()){
                    yongjin += 2 * Convert.objToInt(orderMap.get("goods_num"));
                }else{
                    yongjin += Convert.objToInt(orderMap.get("mcode_money")) - Convert.objToInt(orderMap.get("order_amount"));
                }
            }else if(prole == EnumType.ROLE.白金卡.getRole()){
                // 白金卡推荐超级黑卡 固定2元一单位
                if(role == EnumType.ROLE.超级黑卡.getRole()){
                    yongjin += 2 * Convert.objToInt(orderMap.get("goods_num"));
                }else if(role == EnumType.ROLE.白金卡.getRole()){   // 白金卡推荐白金卡 固定5元一单位
                    yongjin += 5 * Convert.objToInt(orderMap.get("goods_num"));
                }else{
                    yongjin += Convert.objToInt(orderMap.get("mcode_money")) - Convert.objToInt(orderMap.get("order_amount"));
                }
            }else if(prole == EnumType.ROLE.金卡.getRole()){
                // 金卡推荐超级黑卡 固定2元一单位
                if(role == EnumType.ROLE.超级黑卡.getRole()){
                    yongjin += 2 * Convert.objToInt(orderMap.get("goods_num"));
                }else if(role == EnumType.ROLE.白金卡.getRole() || role == EnumType.ROLE.金卡.getRole()){   // 金卡推荐白金卡,金卡 固定5元一单位
                    yongjin += 5 * Convert.objToInt(orderMap.get("goods_num"));
                }else{
                    yongjin += Convert.objToInt(orderMap.get("mcode_money")) - Convert.objToInt(orderMap.get("order_amount"));
                }
            }else if(prole == EnumType.ROLE.普卡.getRole()){
                // 普卡推荐超级黑卡,普卡 固定2元一单位
                if(role == EnumType.ROLE.超级黑卡.getRole() || role == EnumType.ROLE.普卡.getRole()){
                    yongjin += 2 * Convert.objToInt(orderMap.get("goods_num"));
                }else if(role == EnumType.ROLE.白金卡.getRole() || role == EnumType.ROLE.金卡.getRole()){   // 普卡推荐白金卡,金卡 固定5元一单位
                    yongjin += 5 * Convert.objToInt(orderMap.get("goods_num"));
                }
            }else{
                Logger.error("该订单没有上级渠道获得返点.:当前sn："+JSON.toJSONString(orderMap));
                return;
            }
        }else {
            yongjin += 2 * Convert.objToInt(orderMap.get("goods_num"));
        }

        if(yongjin <= 0){
            Logger.error("佣金获取失败订单.:当前sn："+JSON.toJSONString(orderMap));
        }
        addUserMoneyDetail(Convert.objToLong(orderMap.get("uid")),yongjin,Convert.objToInt(orderMap.get("goods_is_discount")),Convert.objToStr(orderMap.get("order_sn")),Convert.objToStr(orderMap.get("date")));
    }

    /**
     * 添加订单分佣明细
     * @param uid
     * @param money
     * @param type
     * @param date
     * @return
     */
    private void addUserMoneyDetail(long uid, int money, int type, String order_sn, String date){
        Map<String,Object> upMap = new HashMap<>();
        upMap.put("uid",uid);
        upMap.put("date",date);
        upMap.put("type",type);
        upMap.put("total_money", money);
        upMap.put("money",money);
        upMap.put("order_sn",order_sn);
        upMap.put("remark", date + "数据分析-订单提成，总佣金："+ money + "，属于自己：" + money);
        orderAnalyDao.addUserMoneyDetail(upMap);
    }

    /**
     * 用户预估\成功收益----UserMoneyExpect\UserMoneyWithdrawalExpect
     * 更新用户金额
     * @param orderList
     * @return
     */
    @Transactional
    public void updateUserMoneyExpect(List<Map<String, Object>> orderList, String source_tab_name, String analy_tab_name){
        long record = 0;
        for(Map<String,Object> orderMap : orderList){
            record = Convert.objToLong(orderMap.get("id"));
            //更新分析表用户及层级关系金额
            updateLevelUserAnalyMoney(orderMap,analy_tab_name);
        }
        //更新分析记录值
        if(record>0) {
            taskDao.updateRecord(record, source_tab_name, analy_tab_name);
        }
    }

    private void updateLevelUserAnalyMoney(Map<String, Object> paramMap,String analy_tab_name){
        double promotion_amount= Convert.objToDouble(paramMap.get("money"));
        String date = Convert.objToStr(paramMap.get("date"));
        String day = date.replaceAll("-", "");
        long uid= Convert.objToLong(paramMap.get("uid"));

        //公用参数
        Map<String,Object> upMap = new HashMap<>();
        upMap.put("date", date);
        upMap.put("day", day);
        upMap.put("tabName", analy_tab_name);
        upMap.put("uid", uid);
        upMap.put("money", promotion_amount);
        if(orderAnalyDao.updateUserAnalyMoney(upMap)==0){
            /* TODO 发送钉钉推送 */
            throw new RuntimeException(String.format("更新用户成功收益失败，金额参数：%s,订单：%s", JSON.toJSONString(upMap),Convert.objToStr(paramMap.get("order_sn"))));
        }
    }

    /**
     * 用户失效收益----UserMoneyInvalidExpect
     * 更新用户金额
     * @param orderList
     * @return
     */
    @Transactional
    public void updateUserMoneyInvalid(List<Map<String, Object>> orderList, String source_tab_name, String analy_tab_name){
        long record = 0;
        for(Map<String,Object> orderMap : orderList){
            record = Convert.objToLong(orderMap.get("id"));
            //更新分析表用户及层级关系金额
            updateLevelUserAnalyMoneyInvalid(orderMap);
        }
        //更新分析记录值
        if(record>0) {
            taskDao.updateRecord(record, source_tab_name, analy_tab_name);
        }
    }

    private void updateLevelUserAnalyMoneyInvalid(Map<String, Object> paramMap){
        double promotion_amount= Convert.objToDouble(paramMap.get("money"));
        String date = Convert.objToStr(paramMap.get("date"));
        String day = date.replaceAll("-", "");
        long uid= Convert.objToLong(paramMap.get("uid"));
        //公用参数
        Map<String,Object> upMap = new HashMap<>();
        upMap.put("date", date);
        upMap.put("day", day);
        upMap.put("uid", uid);
        upMap.put("money", promotion_amount);
        if(orderAnalyDao.updateInvalidMoney(upMap)!=1){
            /* TODO 发送钉钉推送 */
            throw new RuntimeException(String.format("更新用户失效预估金额失败，参数：%s",JSON.toJSONString(upMap)));
        }
    }

    /**
     * 收益结算----UserMoneyWithdrawal
     * 处理可提现金额
     * @param dataList
     * @return
     */
    @Transactional
    public int updateOverOrderMoney(List<Map<String, Object>> dataList){
        int succ = 0;
        for (Map<String,Object> data : dataList){
            System.out.println(String.format("%s当前处理可提现金额第%s条", DateUtil.getDatetime(),succ));
            //添加用户可提现余额
            succ += orderAnalyDao.accumulationUserMoney(data);
        }
        if(dataList.size()!=succ){
            /* TODO 发送钉钉推送 */
            throw new RuntimeException("可提现金额处理失败");
        }
        return succ;
    }

    /**
     * 更新用户订单数
     * @param orderExpectList
     * @return
     */
    @Transactional
    public int updateUserOrderCount(List<Map<String, Object>> orderExpectList, String source_tab_name, String analy_tab_name){
        int count=0;
        long record = 0;
        Map<String,Object> orderParamMap = new HashMap<>();

        for (Map<String,Object> orderMap : orderExpectList) {
            int team_order_count = 1;  //团队订单计数  团队订单默认加1
            int team_order_count_invalid = 0; //团队失效订单计数
            int own_order_count = 0; //个人订单计数
            int own_order_count_invalid = 0; //个人失效订单计数

            record = Convert.objToLong(orderMap.get("id"));
            long uid = Convert.objToLong(orderMap.get("uid"));  //uid
            int type = Convert.objToInt(orderMap.get("type"));  //类型 1 2 自己订单  3 4 团队提成订单 5 6多客长 分公司提团队
            String date = Convert.objToStr(orderMap.get("date"));
            date = date.replaceAll("-","");
            int day = Convert.objToInt(date);
            if(type==1 || type==2){
                own_order_count = 1 ;  //个人订单计数加1
            }
            orderParamMap.put("uid",uid);
            orderParamMap.put("day",day);
            orderParamMap.put("type",1);
            orderParamMap.put("team_order_count",team_order_count);
            orderParamMap.put("team_order_count_invalid",team_order_count_invalid);
            orderParamMap.put("own_order_count",own_order_count);
            orderParamMap.put("own_order_count_invalid",own_order_count_invalid);
            orderAnalyDao.analyOrderCount(orderParamMap);

        }

        //更新分析记录值
        if(record>0) {
            taskDao.updateRecord(record, source_tab_name, analy_tab_name);
        }

        return count;
    }

    /**
     * 更新用户失效订单数
     * @param orderInvalidExpectList
     * @return
     */
    @Transactional
    public int updateUserOrderInvalidCount(List<Map<String, Object>> orderInvalidExpectList, String source_tab_name, String analy_tab_name){
        int count=0;
        long record = 0;
        Map<String,Object> orderParamMap = new HashMap<>();

        for (Map<String,Object> orderMap : orderInvalidExpectList) {
            int team_order_count = 0;  //团队订单计数  团队订单默认加1
            int team_order_count_invalid = 1; //团队失效订单计数
            int own_order_count = 0; //个人订单计数
            int own_order_count_invalid = 0; //个人失效订单计数

            record = Convert.objToLong(orderMap.get("id"));
            long uid = Convert.objToLong(orderMap.get("uid"));  //uid
            int type = Convert.objToInt(orderMap.get("type"));  //类型 1 2 自己订单  3 4 团队提成订单 5 6多客长 分公司提团队
            String date = Convert.objToStr(orderMap.get("date"));
            date = date.replaceAll("-","");
            int day = Convert.objToInt(date);
            if(type==1 || type==2){
                own_order_count_invalid = 1;   //个人失效订单计数加1
            }
            orderParamMap.put("uid",uid);
            orderParamMap.put("day",day);
            orderParamMap.put("team_order_count",team_order_count);
            orderParamMap.put("team_order_count_invalid",team_order_count_invalid);
            orderParamMap.put("own_order_count",own_order_count);
            orderParamMap.put("own_order_count_invalid",own_order_count_invalid);
            orderAnalyDao.analyOrderCount(orderParamMap);

        }

        //更新分析记录值
        if(record>0) {
            taskDao.updateRecord(record, source_tab_name, analy_tab_name);
        }

        return count;
    }

    /**
     *  已发货15天的订单系统自动确认收货
     */
//    @Transactional
    public void success(List<Map<String,Object>> orders){
        List<String> sns = orders.stream().map(x-> Convert.objToStr(x.get("order_sn"))).collect(Collectors.toList());
        orderDao.orderChange(EnumType.ORDER_STATUS.确认收货.getStatus(),sns);
//        orderAnalyDao.changeOrderExpectStatus(EnumType.ORDER_STATUS.确认收货.getStatus(),sns);
    }

    /**
     *  确认收货10天的订单系统自动结算,写入成功订单表
     */
//    @Transactional
    public void over(List<Map<String,Object>> orders){
        List<String> sns = orders.stream().map(x-> Convert.objToStr(x.get("order_sn"))).collect(Collectors.toList());
        orderDao.orderChange(EnumType.ORDER_STATUS.完成.getStatus(),sns);
//        orderAnalyDao.changeOrderExpectStatus(EnumType.ORDER_STATUS.完成.getStatus(),sns);
//        orderDao.orderSuccessSync(orders);
    }
}
